package com.sc.nft.service.impl;

import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.util.IdUtil;
import com.sc.nft.dao.EcologyPoolDao;
import com.sc.nft.dao.EcologyPoolSourceDao;
import com.sc.nft.dao.EcologyPoolSourceDetailDao;
import com.sc.nft.entity.EcologyPool;
import com.sc.nft.entity.EcologyPoolRecord;
import com.sc.nft.entity.EcologyPoolSourceDetail;
import com.sc.nft.enums.*;
import com.sc.nft.exception.GlobalRunTimeException;
import com.sc.nft.service.EcologyPoolSourceDetailService;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.redisson.Redisson;
import org.redisson.api.RLock;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.math.BigDecimal;
import java.util.Date;
import java.util.List;
import java.util.concurrent.TimeUnit;

/**
 * @author PC
 * @description 针对表【sc_ecology_pool_source_detail(生态池-生态熔炼积分-积分明细)】的数据库操作Service实现
 * @createDate 2024-07-20 11:27:02
 */
@Slf4j
@RequiredArgsConstructor
@Service
public class EcologyPoolSourceDetailServiceImpl implements EcologyPoolSourceDetailService {
    private final EcologyPoolSourceDetailDao ecologyPoolSourceDetailDao;
    private final Redisson redisson;
    private final EcologyPoolDao ecologyPoolDao;
    private final EcologyPoolSourceDao ecologyPoolSourceDao;

    @Override
    public List<EcologyPoolSourceDetail> getLeDateList() {
        return ecologyPoolSourceDetailDao.getLeDateList();
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void pointsDistribution(Date date, EcologyPoolSourceDetail ecologyPoolSourceDetail) {
        // 把积分分配给官方的账户池.做一条记录,锁使用官方池锁
        String key = RedisKeyEnum.ECOLOGY_POOL_ALLOCATE.getKey();
        RLock lock = redisson.getLock(key);
        try {
            if (!lock.tryLock(3, TimeUnit.MINUTES)) {
                log.error("获取锁失败");
                return;
            }
            // 向官方池内分配积分,判定官方池是否存在,存在了直接sql加,不存在的话就新增一条
            EcologyPool ecologyPool = ecologyPoolDao.getByType(EcologyPoolTypeEnum.OFFICIAL, EcologyPoolLinkTypeEnum.POINTS);
            if (BeanUtil.isEmpty(ecologyPool)) {
                // 新增一条
                EcologyPool save = new EcologyPool();
                save.setLinkCount(ecologyPoolSourceDetail.getLinkCount());
                save.setLinkType(ecologyPoolSourceDetail.getLinkType());
                save.setDaoId(6L);
                save.setUserId(0L);
                save.setPoolType(EcologyPoolTypeEnum.OFFICIAL);
                save.buildPkCode();
                save.setVersion(1);
                save.insert();
                // 记录流水日志
                EcologyPoolRecord ecologyPoolRecord = new EcologyPoolRecord();
                ecologyPoolRecord.setLinkCount(ecologyPoolSourceDetail.getLinkCount());
                ecologyPoolRecord.setLinkType(ecologyPoolSourceDetail.getLinkType());
                ecologyPoolRecord.setBeforeLinkCount(BigDecimal.ZERO);
                ecologyPoolRecord.setAfterLinkCount(ecologyPoolSourceDetail.getLinkCount());
                ecologyPoolRecord.setIsAdd(Boolean.TRUE);
                ecologyPoolRecord.setDaoId(6L);
                ecologyPoolRecord.setUserId(0L);
                ecologyPoolRecord.setPoolType(EcologyPoolTypeEnum.OFFICIAL);
                ecologyPoolRecord.setOperationType(EcologyPoolOperationTypeEnum.RELEASE);
                ecologyPoolRecord.setFlowType(EcologyPoolFlowTypeEnum.IN_FLOW);
                ecologyPoolRecord.setSourcePoolType(EcologyPoolTypeEnum.OFFICIAL);
                ecologyPoolRecord.setSourceDaoId(0L);
                ecologyPoolRecord.setSourceUserId(0L);
                ecologyPoolRecord.setRemark("积分分配给官方池");
                ecologyPoolRecord.setTransactionUuid(IdUtil.simpleUUID());
                ecologyPoolRecord.insert();
                // 根据pkCode对释放天数+1 待释放-1 已释放积分+linkCount 待释放积分-linkCount
                ecologyPoolSourceDao.released(ecologyPoolSourceDetail.getPkCode(), ecologyPoolSourceDetail.getLinkCount());
                return;
            }

            // 官方池存在,直接加
            ecologyPoolDao.increasePoints(ecologyPool.getId(), ecologyPoolSourceDetail.getLinkCount(), ecologyPool.getVersion());
            // 记录流水日志
            EcologyPoolRecord ecologyPoolRecord = new EcologyPoolRecord();
            ecologyPoolRecord.setLinkCount(ecologyPoolSourceDetail.getLinkCount());
            ecologyPoolRecord.setLinkType(ecologyPoolSourceDetail.getLinkType());
            ecologyPoolRecord.setBeforeLinkCount(ecologyPool.getLinkCount());
            ecologyPoolRecord.setAfterLinkCount(ecologyPoolSourceDetail.getLinkCount().add(ecologyPool.getLinkCount()));
            ecologyPoolRecord.setIsAdd(Boolean.TRUE);
            ecologyPoolRecord.setDaoId(6L);
            ecologyPoolRecord.setUserId(0L);
            ecologyPoolRecord.setPoolType(EcologyPoolTypeEnum.OFFICIAL);
            ecologyPoolRecord.setOperationType(EcologyPoolOperationTypeEnum.RELEASE);
            ecologyPoolRecord.setFlowType(EcologyPoolFlowTypeEnum.IN_FLOW);
            ecologyPoolRecord.setSourcePoolType(EcologyPoolTypeEnum.OFFICIAL);
            ecologyPoolRecord.setSourceDaoId(0L);
            ecologyPoolRecord.setSourceUserId(0L);
            ecologyPoolRecord.setRemark("积分分配给官方池");
            ecologyPoolRecord.setTransactionUuid(IdUtil.simpleUUID());
            ecologyPoolRecord.insert();
            ecologyPoolSourceDetailDao.releasedSuccess(ecologyPoolSourceDetail.getId());
            // 根据pkCode对释放天数+1 待释放-1 已释放积分+linkCount 待释放积分-linkCount
            ecologyPoolSourceDao.released(ecologyPoolSourceDetail.getPkCode(), ecologyPoolSourceDetail.getLinkCount());
        } catch (Exception e) {
            e.printStackTrace();
            throw new GlobalRunTimeException(e.getMessage());
        } finally {
            if (lock.isLocked() && lock.isHeldByCurrentThread()) {
                lock.unlock();
            }
        }
    }
}




